home *** CD-ROM | disk | FTP | other *** search
- #include "mgP.h"
- #include "mgribP.h"
- #include "mgribtoken.h"
- #include "polylistP.h"
-
- #define MAXCLINE 999999
- void mgrib_drawPline(HPoint3 *p1, HPoint3 *p2);
- void mgrib_drawCline(HPoint3 *p1, HPoint3 *p2);
-
- void mgrib_polygon( int nv, HPoint3 *v, int nn, Point3 *n,
- int nc,ColorA *c );
- void mgrib_mesh( int wrap,int nu,int nv,HPoint3 *p, Point3 *n,ColorA *c );
- void mgrib_line( HPoint3 *p1, HPoint3 *p2 );
- void mgrib_polyline( int nv, HPoint3 *verts, int nc, ColorA *colors,
- int wrapped );
- void mgrib_polylist( int np, Poly *p, int nv, Vertex *v,
- int plflags );
- void mgrib_drawnormal(HPoint3 *p, Point3 *n);
-
-
-
- /*-----------------------------------------------------------------------
- * Function: mgrib_polygon
- * Description: draw a polygon
- * Author: wisdom
- * Date: Thu Aug 26 13:46:25 CDT 1993
- * Notes: See mg.doc.
- *
- */
- void
- mgrib_polygon(int nv, HPoint3 *V,
- int nn, Point3 *N,
- int nc, ColorA *C)
- {
- register int i;
- register HPoint3 *v;
- register Point3 *n;
- register Color *c;
- register ColorA *c4;
- HPoint3 hpt;
- int flag;
- int shading;
- int matover;
- int ninc;
-
- flag = _mgc->astk->ap.flag;
- shading = _mgc->astk->ap.shading;
- matover = _mgc->astk->mat.override;
- ninc = (nn > 1);
- if ((matover & MTF_DIFFUSE) && !_mgc->astk->useshader) nc = 0;
-
- mrti(mr_polygon,mr_NULL);
-
- /* Points */
- if(nv>0 && (flag & APF_FACEDRAW)) {
- mrti(mr_P,mr_buildarray, nv*3, mr_NULL);
- for(i = 0; i < nv; i++) {
- /* we cannot descibe a polygon using Pw, so we normalize */
- HPt3Normalize(&V[i], &hpt);
- mrti(mr_subarray3, &hpt, mr_NULL);
- }
- }
-
- /* Supply Color (explicit) */
- if (nc>0 && (flag & APF_FACEDRAW) && !(flag & APF_CONSTANT)) {
- /* note:color should already be set in case of APF_CONSTANT,no? */
- mrti(mr_Cs, mr_buildarray, nv*3, mr_NULL);
- for(i = 0; i < nv; i++) {
- if(nc>1) c4 = &C[i]; else c4 = C;
- mrti(mr_subarray3, (float *)c4, mr_NULL);
- }
- }
-
- /* Supply Transparency */
- if(nc>0 && flag & APF_TRANSP && !(matover & MTF_ALPHA)) {
- mrti(mr_Os, mr_buildarray, nv*3, mr_NULL);
- for(i = 0; i < nv; i++) {
- float opacity[3];
- if(nc>1) c4 = &C[i]; else c4 = C;
- opacity[0]=opacity[1]=opacity[2]=c4->a;
- mrti(mr_subarray3, opacity, mr_NULL);
- }
- }
- /* Supply Normals */
- if (nn>0 && (flag & APF_FACEDRAW) && !(flag & APF_CONSTANT)) {
- mrti(mr_N, mr_buildarray, nv*3, mr_NULL);
- for(i = 0; i < nv; i++) {
- if(nn>1) n = &N[i]; else n = N;
- mrti(mr_subarray3, n, mr_NULL);
- }
- }
-
- /* Draw Edges */
- if(flag & APF_EDGEDRAW) {
- c = &_mgc->astk->ap.mat->edgecolor;
- mrti(mr_attributebegin,
- mr_surface, mr_constant,
- mr_color, mr_parray, 3, c,
- mr_opacity, mr_array, 3, 1., 1., 1., mr_NULL);
-
- for(i=0;i<nv-1;i++) mgrib_drawline(&V[i],&V[i+1]);
- mgrib_drawline(&V[i],&V[0]);
- mrti(mr_attributeend, mr_NULL);
- }
-
- /* Draw Normals */
- if(flag & APF_NORMALDRAW) {
- for (n = N, v = V, i = 0; i<nv; ++i, ++v, n += ninc)
- mgrib_drawnormal(v, n);
- }
- }
-
- /*-----------------------------------------------------------------------
- * Function: mgrib_line
- * Description: draws a line
- * Author: wisdom
- * Date: Fri Jan 17 14:31:06 CST 1992
- * Notes: see mg.doc
- */
- void mgrib_line( HPoint3 *p1, HPoint3 *p2 )
- {
- mrti(mr_attributebegin, mr_surface, mr_constant, mr_NULL);
- mgrib_drawline(p1,p2);
- mrti(mr_attributeend, mr_NULL);
- }
-
- /*-----------------------------------------------------------------------
- * Function: mgrib_drawline, mgrib_drawPline, mgrib_drawCline, bounded
- * Description: draws a line for rman.
- * Returns: nothing
- * Author: wisdom, gunn, slevy, munzner
- * Date: Tue Feb 18 14:20:29 CST 1992
- * Notes:
- */
- void
- mgrib_drawline(HPoint3 *p1, HPoint3 *p2)
- {
- if(_mgribc->line_mode==MG_RIBPOLYGON) mgrib_drawPline(p1,p2);
- if(_mgribc->line_mode==MG_RIBCYLINDER) mgrib_drawCline(p1,p2);
- if(_mgribc->line_mode==MG_RIBPRMANLINE)
- NotImplemented("MG_RIBPRMANLINE");
- }
-
- void
- mgrib_drawPline(HPoint3 *p1, HPoint3 *p2)
- {
- Transform V;
- Transform P2S,O2S, O2P, P2O, S2O;
- int xsize, ysize;
- HPoint3 pnts[4], pnts2[4];
- HPoint3 s1, s2;
- int i;
- float dx,dy,k, len;
-
- /* This code will simulate line drawing in Photorman */
- /* create obj->proj transform */
- CamView(_mgc->cam, V); /* world->proj */
- TmConcat(_mgc->xstk->T, V, O2P); /* obj->proj */
-
- /* create obj->screen transform */
- WnGet(_mgc->win, WN_XSIZE, &xsize);
- WnGet(_mgc->win, WN_YSIZE, &ysize);
- TmScale(P2S, (float)xsize, (float)ysize, 1.0);
- TmConcat(O2P, P2S, O2S);
-
- /* translate & dehomogenize line endpoints from object to screen */
- HPt3TransPt3(O2S, p1, &s1);
- HPt3TransPt3(O2S, p2, &s2);
-
- dy = s2.y - s1.y;
- dx = s2.x - s1.x;
- len = hypot(dy,dx);
- k = _mgc->astk->ap.linewidth / len;
-
- pnts[0].x = s1.x -dy * k;
- pnts[0].y = s1.y +dx * k;
- pnts[1].x = s1.x +dy * k;
- pnts[1].y = s1.y -dx * k;
- pnts[2].x = s2.x +dy * k;
- pnts[2].y = s2.y -dx * k;
- pnts[3].x = s2.x -dy * k;
- pnts[3].y = s2.y +dx * k;
-
- pnts[0].z = s1.z;
- pnts[1].z = s1.z;
- pnts[2].z = s2.z;
- pnts[3].z = s2.z;
-
- for (i=0; i<4; ++i) pnts[i].w = 1.0;
-
- /* now project back... */
- /* first, find S2O transform */
- TmInvert(O2S, S2O);
-
- /* now transform screen coords to object coords */
-
- /* DRAW HERE */
- mrti(mr_polygon, mr_P, mr_buildarray, 4*3, mr_NULL);
- for(i=0;i<4;i++) {
- HPoint3 pt;
-
- HPt3Transform(S2O, &pnts[i], &pt);
- HPt3Normalize(&pt, &pt);
- mrti(mr_subarray3, &pt, mr_NULL);
- }
- }
-
- void
- mgrib_drawCline(HPoint3 *p1, HPoint3 *p2)
- {
- Pt3Coord angle,length;
- Point3 t,xn,yn,axis;
- Point3 start, end;
- HPoint3 Hstart, Hend;
- static float unitz[3] = {0.0, 0.0, 1.0};
- float radius = .005;
- float size;
- int bounded(Point3 *p);
-
- HPt3Normalize(p1, &Hstart);
- HPt3Normalize(p2, &Hend);
-
- start.x = Hstart.x;
- start.y = Hstart.y;
- start.z = Hstart.z;
-
- end.x = Hend.x;
- end.y = Hend.y;
- end.z = Hend.z;
-
- if (! Pt3Equal(&start,&end)) {
- size = radius*_mgc->astk->ap.linewidth;
- Pt3Sub(&end,&start,&t);
- length = Pt3Length(&t);
- Pt3Cross((Point3*)unitz,&t,&axis);
- Pt3Unit(&t);
- angle = Pt3Dot((Point3*)unitz,&t);
- angle = acos(angle);
- mrti(mr_transformbegin, mr_NULL);
- if (bounded(&start))
- mrti(mr_translate,
- mr_float, start.x,
- mr_float, start.y,
- mr_float, start.z, mr_NULL);
- if ( (t.x == 0.0) && (t.y == 0.0) && (t.z < 0.0)) {
- /* if along negative z axis cross product is 0
- but rotation by 180 degrees is necessary
- (angle is computed correctly) */
- axis.y = 1.0;
- }
- if (bounded(&axis))
- mrti(mr_rotate, mr_float, DEGREES(angle),
- mr_float, axis.x, mr_float, axis.y, mr_float, axis.z, mr_NULL);
- if (length < MAXCLINE)
- mrti(mr_cylinder, mr_float, size, mr_float, 0.,
- mr_float, length, mr_float, 360., mr_NULL);
- mrti(mr_transformend, mr_NULL);
- }
- }
-
- int
- bounded(p)
- Point3 *p;
- {
- if (! Pt3Equal(p,&Pt3Origin)) {
- if (p->x < MAXCLINE && p->y < MAXCLINE && p->z < MAXCLINE)
- return 1;
- } else {
- return 0;
- }
- }
-
-
-
- /*-----------------------------------------------------------------------
- * Function: mgrib_polyline
- * Description: draws a Polyline
- * Author: wisdom
- * Date: Fri Jan 17 14:31:06 CST 1992
- * Notes: see mg.doc
- */
- void mgrib_polyline( int nv, HPoint3 *v, int nc, ColorA *c, int wrapped )
- {
- ColorA *color;
-
- mrti(mr_attributebegin, mr_surface, mr_constant, mr_NULL);
- if(nc==0) mrti(mr_color, mr_parray, 3,
- &_mgc->astk->mat.edgecolor, mr_NULL);
- if(nc==1) mrti(mr_color, mr_parray, 3, c, mr_NULL);
- if(nv == 1) {
- mgrib_drawpoint(v);
- }
- else {
- if(wrapped & 1) {
- if(nc > 1) {
- color = c + nc - 1;
- mrti(mr_color, mr_parray, 3, color, mr_NULL);
- }
- mgrib_drawline(v + nv - 1,v);
- }
-
- while(--nv > 0) {
- if(nc > 1) {
- color = c++;
- mrti(mr_color, mr_parray, 3, color, mr_NULL);
- }
- mgrib_drawline(v,(v+1));
- v++;
- }
- }
-
- mrti(mr_attributeend, mr_NULL);
-
- }
-
- /*-----------------------------------------------------------------------
- * Function: mgrib_drawpoint
- * Description: draws a point for rman.
- * Returns: nothing
- * Author: wisdom
- * Date: Fri Mar 13 15:04:01 CST 1992
- * Notes:
- */
-
- void
- mgrib_drawpoint(HPoint3 *p)
- {
- float radius = 0.005;
- float size = radius*_mgc->astk->ap.linewidth;
-
- mrti(mr_transformbegin, mr_NULL);
- mrti(mr_translate, mr_float, p->x, mr_float, p->y,
- mr_float, p->z, mr_NULL);
- mrti(mr_sphere, mr_float, size, mr_float, size, mr_float, -size,
- mr_float, 360., mr_NULL);
- mrti(mr_transformend, mr_NULL);
- }
-
- /*-----------------------------------------------------------------------
- * Function: mgrib_polylist
- * Description: draws a Polylist: linked list of Polys
- * Author: wisdom
- * Date: Wed Jan 22 16:07:03 CST 1992
- * Notes: see mg.doc
- */
- void mgrib_polylist( int np, Poly *P, int nv, Vertex *V, int plflags )
- {
- register int i,j;
- register Poly *p;
- register Vertex **v, *vp;
- register Point3 *n;
- HPoint3 hpt;
- int flag,shading,matover;
- Color *color;
- ColorA *colorA;
-
-
- flag = _mgc->astk->ap.flag;
- shading = _mgc->astk->ap.shading;
- matover = _mgc->astk->mat.override;
-
- if((matover & MTF_DIFFUSE) && !_mgc->astk->useshader)
- plflags &= ~(PL_HASVCOL | PL_HASPCOL);
-
- if (shading & APF_CONSTANT) plflags &= ~(PL_HASVN|PL_HASPN);
- else if (shading & APF_FLAT) plflags &= ~PL_HASVN;
- else if (shading & APF_SMOOTH) plflags &= ~PL_HASPN;
-
- if (flag & APF_FACEDRAW) {
- mrti(mr_attributebegin, mr_NULL);
- for (p = P, i = 0; i < np; i++, p++) {
-
- /* per polygon color */
- if (plflags & PL_HASPCOL) {
- mrti(mr_color, mr_parray, 3, &p->pcol, mr_NULL);
- /* then per-polygon transparency, if defined */
- if (flag & APF_TRANSP && !(matover & MTF_ALPHA)) {
- mrti(mr_Os, mr_array, 3,
- p->pcol.a, p->pcol.a, p->pcol.a, mr_NULL);
- }
- }
- switch (p->n_vertices) {
- case 1:
- v = p->v;
- mrti(mr_attributebegin, mr_NULL);
- if(plflags & PL_HASVCOL)
- mrti(mr_color, mr_parray, 3, &(*v)->vcol, mr_NULL);
- mrti(mr_surface, mr_constant,
- mr_opacity, mr_array, 3, 1., 1., 1., mr_NULL);
- mgrib_drawpoint((HPoint3 *)(*v));
- mrti(mr_attributeend, mr_NULL);
- break;
- case 2:
- v = p->v;
- mrti(mr_attributebegin, mr_NULL);
- if(plflags & PL_HASVCOL)
- mrti(mr_color, mr_parray, 3, &(*v)->vcol, mr_NULL);
- mrti(mr_surface, mr_constant,
- mr_opacity, mr_array, 3, 1., 1., 1., mr_NULL);
- mgrib_drawline((HPoint3 *)*v,(HPoint3*)*(v+1));
- mrti(mr_attributeend, mr_NULL);
- break;
- default:
- mrti(mr_polygon, mr_NULL);
-
- /* do points */
- mrti(mr_P, mr_buildarray, p->n_vertices*3, mr_NULL);
- for (j=0, v=p->v; j < p->n_vertices; j++, v++) {
- HPt3Normalize(&(*v)->pt, &hpt);
- mrti(mr_subarray3, &hpt, mr_NULL);
- }
-
- /* colors, if supplied */
- if(plflags & PL_HASVCOL) {
- mrti(mr_Cs, mr_buildarray, p->n_vertices*3, mr_NULL);
- for (j=0, v=p->v; j < p->n_vertices; j++, v++) {
- mrti(mr_subarray3, &(*v)->vcol, mr_NULL);
- }
- /* then per-vertex transparency, if defined */
- if(flag & APF_TRANSP && !(matover & MTF_ALPHA)) {
- mrti(mr_Os, mr_buildarray, p->n_vertices*3, mr_NULL);
- for (j=0, v=p->v; j < p->n_vertices; j++, v++) {
- float opacity[3];
- opacity[0]=opacity[1]=opacity[2]=(*v)->vcol.a;
- mrti(mr_subarray3, opacity, mr_NULL);
- }
- }
- }
-
- /* now normals, if supplied */
- if(plflags & PL_HASVN) {
- mrti(mr_N, mr_buildarray, p->n_vertices*3, mr_NULL);
- for (j=0, v=p->v; j < p->n_vertices; j++, v++) {
- mrti(mr_subarray3, &((*v)->vn), mr_NULL);
- }
- } else if(plflags & PL_HASPN) {
- mrti(mr_N, mr_buildarray, p->n_vertices*3, mr_NULL);
- for(j=0, v=p->v; j< p->n_vertices; j++, v++) {
- mrti(mr_subarray3, &(p->pn), mr_NULL);
- }
- }
- break;
- }
- }
- mrti(mr_attributeend, mr_NULL);
- }
- if (flag & APF_EDGEDRAW) {
- color = &_mgc->astk->ap.mat->edgecolor;
- mrti(mr_attributebegin, mr_surface, mr_constant,
- mr_color, mr_parray, 3, color,
- mr_opacity, mr_array, 3, 1., 1., 1., mr_NULL);
-
- for (p = P, i = 0; i < np; i++, p++) {
- for (j=0, v=p->v; j < (p->n_vertices-1); j++, v++) {
- mgrib_drawline((HPoint3 *)*v,(HPoint3*)*(v+1));
- }
- mgrib_drawline((HPoint3 *)*v,(HPoint3 *)*(p->v));
- }
- mrti(mr_attributeend,mr_NULL);
- }
-
-
- if (flag & APF_NORMALDRAW) {
- /* since mg_drawnormal handles attributes and stacking, we do nothing here */
- if (plflags & PL_HASPN) {
- for (p = P, i = 0; i < np; i++, p++) {
- for (j=0, v=p->v; j < p->n_vertices; j++, v++) {
- mgrib_drawnormal(&(*v)->pt, &p->pn);
- }
- }
- } else if (plflags & PL_HASVN) {
- for (vp = V, i = 0; i < nv; i++, vp++) {
- mgrib_drawnormal(&vp->pt, &vp->vn);
- }
- }
- }
-
- }
-
- /* There is a basic problem now with 4-d points and 3-d normal vectors.
- For now, we'll just ignore the 4-th coordinate of the point when
- computing the tip of the normal vector. This will work OK with all
- existing models, but for genuine 4-d points it won't work. But,
- come to think of it, what is the correct interpretation of the
- normal vector when the points live in 4-d?
- */
- void
- mgrib_drawnormal(HPoint3 *p, Point3 *n) {
- HPoint3 end, tp;
- float scale;
- Color *color;
-
- if (p->w <= 0.0) return;
- scale = p->w * _mgc->astk->ap.nscale;
- end.x = p->x + scale*n->x;
- end.y = p->y + scale*n->y;
- end.z = p->z + scale*n->z;
- end.w = p->w;
-
- color = &_mgc->astk->mat.normalcolor;
- mrti(mr_attributebegin, mr_surface, mr_constant,
- mr_color, mr_parray, 3, color,
- mr_opacity, mr_array, 3, 1., 1., 1., mr_NULL);
- mgrib_drawline(&tp,&end);
- mrti(mr_attributeend, mr_NULL);
-
- }
-
- void
- mgrib_bezier( int du, int dv, int dimn, float *CtrlPnts, float *txmapst, ColorA *c )
- {
- int i, ip, nu, nv;
- static float *uknot=NULL, *vknot=NULL;
- static size_t ulen=0,vlen=0;
- size_t nulen=0, nvlen=0;
- int flag = _mgc->astk->ap.flag;
- int matover = _mgc->astk->mat.override;
-
- du += 1;
- dv += 1;
- nu = du;
- nv = dv;
- ip = nu * nv * dimn;
-
- if(!uknot) {
- ulen=nu+du;
- uknot=(float *)malloc(ulen*sizeof(float));
- }
- if(!vknot) {
- vlen=nv+dv;
- vknot=(float *)malloc(vlen*sizeof(float));
- }
- nulen=nu+du;
- nvlen=nv+dv;
- if(nulen>ulen) uknot=(float *)realloc(uknot,(ulen=nulen)*sizeof(float));
- if(nvlen>vlen) vknot=(float *)realloc(vknot,(vlen=nvlen)*sizeof(float));
-
- /* uknot = (float *)malloc((nu+du)*sizeof(float)); */
- for(i=0;i<nu;i++) uknot[i] = 0;
- for(i=nu;i<(nu+du);i++) uknot[i] = 1;
-
- /* vknot = (float *)malloc((nv+dv)*sizeof(float)); */
- for(i=0;i<nv;i++) vknot[i] = 0;
- for(i=nv;i<(nv+dv);i++) vknot[i] = 1;
-
- mrti(mr_nupatch, mr_int, nu, mr_int, du, mr_NULL);
- mrti(mr_parray, (nu+du), uknot, mr_NULL);
- mrti(mr_int, 0, mr_int, (nu-1), mr_int, nv, mr_int, dv, mr_NULL);
- mrti(mr_parray, (nv+dv), vknot, mr_NULL);
- mrti(mr_int, 0, mr_int, nv -1, mr_NULL);
-
- mrti(dimn == 3 ? mr_P : mr_Pw,
- mr_parray, ip, CtrlPnts, mr_NULL);
-
- /* free(uknot); */
- /* free(vknot); */
-
- if(c && !( (matover & MTF_DIFFUSE) && !_mgc->astk->useshader) ) {
- mrti(mr_Cs, mr_buildarray, 12, mr_NULL);
- for (i = 0; i < 4; i++) {
- mrti(mr_subarray3, (float *)&c[i], mr_NULL);
- }
- if(flag & APF_TRANSP && !(matover & MTF_ALPHA)) {
- float opacity[3];
- opacity[0]=opacity[1]=opacity[2]=c[i].a;
- mrti(mr_Os, mr_buildarray, 12, mr_NULL);
- for (i = 0; i < 4; i++) {
- mrti(mr_subarray3, opacity, mr_NULL);
- }
- }
- }
-
- if(txmapst) {
- mrti(mr_nl, mr_st, mr_parray, 8, txmapst, mr_NULL);
- }
- }
-